/*
 * To change this template, choose Tools | Templates
 * and open the template in the editor.
 */
package GestureRecognition;

import coordinates.ConvexHull;
import java.awt.AWTException;
import java.awt.Robot;
import java.awt.event.KeyEvent;
import java.util.logging.Level;
import java.util.logging.Logger;
/**
 *
 * @author HOME
 */
public class Gestures {

    private ConvexHull ch = new ConvexHull();
    static int frameCount = 0;
    private int[] preLargestTip;
    private int[] preSecondLargestTip;
    private int[] LargestTip;
    private int[] SecondLargestTip;
    final int MIN_ROTATE = 10;
    final int MAX_SLIDE = 5;
    final int MAX_SCROLL = 5;
    final int MAX_FRAME_COUNT = 3;

    public void identifyGestureType(int[] largestCont, int[] secondLargestCont, boolean isConsecutive) {

        if (!isConsecutive) {
            frameCount = 0;
            return;

        } else {
            if (frameCount == 0) {
                preLargestTip = largestCont;
                preSecondLargestTip = secondLargestCont;
                frameCount++;
                return;

            } else if (frameCount < MAX_FRAME_COUNT) {
                frameCount++;
                return;

            } else {
                frameCount = 0;
                LargestTip = largestCont;
                SecondLargestTip = secondLargestCont;

                int diffLargeX = LargestTip[0] - preLargestTip[0];
                int diffLargeY = LargestTip[1] - preLargestTip[1];
                int diffSecondLargeX = SecondLargestTip[0] - preSecondLargestTip[0];
                int diffSecondLargeY = SecondLargestTip[1] - preSecondLargestTip[1];


                if ((Math.abs(diffLargeY)) > MIN_ROTATE && (Math.abs(diffSecondLargeY)) > MIN_ROTATE) { // Rotate starting from horizontal

                    if ((diffLargeX - diffSecondLargeX) < MAX_SCROLL) { // Vertical Scroll
                        int dir = (int) Math.copySign(1, diffLargeY);
                        // +1: Down
                        // -1: Up
                        scroll(dir);
                    } else {
                        int dir = (int) Math.copySign(1, diffLargeY);
                        // +1: anticlockwise ****should be the least point in x
                        // -1: Clockwise

                        double angle1 = Math.atan2(LargestTip[1] - SecondLargestTip[1], LargestTip[0] - SecondLargestTip[0]);
                        double angle2 = Math.atan2(preLargestTip[1] - preSecondLargestTip[1], preLargestTip[0] - preSecondLargestTip[0]);
                        double angle = angle1 - angle2;
                        rotate(dir, angle);
                    }

                } else if ((diffLargeX - diffSecondLargeX) < MAX_SLIDE) { // Horizontal Slide
                    int dir = (int) Math.copySign(1, diffLargeX);
                    // +1: Right Side
                    // -1: Left Side

                    slide(dir);

                } else { // Zoom
                    int magZoom = (Math.abs(LargestTip[0] - SecondLargestTip[0]) - Math.abs(preLargestTip[0] - preSecondLargestTip[0])) / 2;
                    int dir = (int) Math.copySign(1, magZoom);
                    // +1: Zoom Out
                    // -1: Zoom In
                 //   zooming(dir, Math.abs(magZoom));

                }
            }
        }
    }

    public void rotate(int dir, double angle) {
        System.out.println("Rotate");
        System.out.println("Direction= " + dir);
        System.out.println("Angle= " + angle);
    }

//    public void scroll(int dir) {
//        System.out.println("Scroll");
//        System.out.println("Direction= " + dir);
//    }


    
     public void slide(int direction){
        try {
            Robot rb = new Robot();
            switch (direction) {
                case -1:
                {
                    rb.keyPress(KeyEvent.VK_LEFT);
                    rb.keyRelease(KeyEvent.VK_LEFT);
                }
                case +1:
                {
                    rb.keyPress(KeyEvent.VK_RIGHT);
                    rb.keyRelease(KeyEvent.VK_RIGHT);
                }
                case 3:
                {
                    rb.keyPress(KeyEvent.VK_UP);
                    rb.keyRelease(KeyEvent.VK_UP);
                }
                case 4:
                {
                    rb.keyPress(KeyEvent.VK_DOWN);
                    rb.keyRelease(KeyEvent.VK_DOWN);
                }

            }
        } catch (AWTException ex) {
            Logger.getLogger(Gestures.class.getName()).log(Level.SEVERE, null, ex);
        }
    }


    public void scroll(int distance){
        try {
            //distance=# of wheels
            Robot rb = new Robot();
            rb.mouseWheel(distance);
        } catch (AWTException ex) {
            Logger.getLogger(Gestures.class.getName()).log(Level.SEVERE, null, ex);
        }

    }


    public void zooming(int factor) {
        try {
            Robot rb = new Robot();
            if (factor > 0) {
                //Zoom in
                rb.keyPress(KeyEvent.VK_CONTROL);
                rb.keyPress(KeyEvent.VK_SHIFT);
                rb.keyPress(KeyEvent.VK_EQUALS);
                rb.keyRelease(KeyEvent.VK_CONTROL);
                rb.keyRelease(KeyEvent.VK_SHIFT);
                rb.keyRelease(KeyEvent.VK_EQUALS);
            } else {
                //Zoom out
                rb.keyPress(KeyEvent.VK_CONTROL);
                rb.keyPress(KeyEvent.VK_SHIFT);
                rb.keyPress(KeyEvent.VK_MINUS);
                rb.keyRelease(KeyEvent.VK_CONTROL);
                rb.keyRelease(KeyEvent.VK_SHIFT);
                rb.keyRelease(KeyEvent.VK_MINUS);

            }
        } catch (AWTException ex) {
            Logger.getLogger(Gestures.class.getName()).log(Level.SEVERE, null, ex);
        }
    }
}
